#ifndef ENTITY7_1_CPP
#define ENTITY7_1_CPP

#include "Entity7.h"
#include<utility>
#include<cstdio>
#include<stdlib.h>
using std::pair;
using std::make_pair;
class Entity7_do
{
	public :
		int startGame(const GameType &cn, int cm, const chessBoard &Boa)
		{
			typ = cn; role = cm;
			n = Boa.n; m = Boa.m;
			for(int i = 1; i<=n; i++) for(int j = 1; j<=m; j++) a[i][j] = Boa.a[i][j];
			do_prepare();
			return 0;
		}
		pair<int, int> playChess()
		{
			return do_playChess();
		}
		void setPos(pair<int, int> cn, int cm)
		{
			a[cn.first][cn.second] = cm;
			do_setPos(cn, cm);
		}
		int endGame(int cn)
		{
			do_endGame(cn);
			return 0;
		}
	private :
		typedef long long LL;
		LL get_r(LL cn) {return (rand()*RAND_MAX+rand())%cn; }
		LL get_n(LL cn, LL cm) {return cn + get_r(cm-cn+1); }
		GameType typ;
		int role;
		int n, m;
		int a[MaxBoardSize+1][MaxBoardSize+1];
		LL f[55][55], mi[55];
		int zhan[55];
		LL ans, Maxnum;
		int Num1, Num2, Num3, Num4, Num5, Num6;
		const int dx[4] = {-1,0,1,1};
		const int dy[4] = {1,1,1,0};
		void do_endGame(int winner) {return; }
		void do_setPos(pair<int, int> cn, int cm) {return; }
		void do_prepare()
		{
			Num1 = 30, Num2 = 900, Num3 = 40, Num4 = 90, Num5 = 799, Num6 = 10;
			mi[0] = 1; mi[1] = Num1;
			for(int i = 2;i<=typ.len;i++) mi[i] = 1ll*mi[i-1]*Num2;
			return;
		}
		void swap(int &cn, int &cm) {int cx = cn; cn = cm; cm = cx; }
		void do_geng(int b, int w, int cn)
		{
			if(role == 2) swap(b, w);
			ans = ans + get_n(0,(b+w)?Num5:Num6);
			if(b && w) return;
			if(b) {ans = ans + 1ll*mi[b]*cn; return; }
			if(w <= typ.len-3) ans = ans - 1ll*mi[w]*cn*Num3;
			else ans = ans - 1ll*mi[w]*cn*Num4;
		}
		void geng()
		{
			int b = 0, w = 0; 
			int lei = 0, xian = 0;
			for(int i = 1;i<=typ.len;i++)
			{
				if(zhan[i] == colorEmpty) lei = lei+xian*xian, xian = 0;
				if(zhan[i] == colorBlack) xian++, b++;
				if(zhan[i] == colorWhite) xian++, w++;
			}
			lei = lei+xian*xian, xian = 0;
			do_geng(b, w, lei);
		}
		int in_range(int cn, int cl, int cr) {return cl<=cn && cn<=cr; }
		LL calc_value()
		{
			ans = 0;
			int bx = typ.len;
			for(int i = 1;i<=n;i++) for(int j = 1;j<=m;j++) for(int ij = 0;ij<=3;ij++)
			{
				if(!in_range(i+(typ.len-1)*dx[ij], 1, n) || !in_range(j+(typ.len-1)*dy[ij], 1, m)) continue;
				for(int ik = 1;ik<=typ.len;ik++) zhan[ik] = a[i+(ik-1)*dx[ij]][j+(ik-1)*dy[ij]];
				geng();
			}
			return ans;
		}
		pair<int, int> get_max_pos()
		{
			int X=-1,Y=-1;
			LL g=-LONG_LONG_MAX;
			for(int i=1; i<=n; ++i)
				for(int j=1; j<=n; ++j)
					if(a[i][j]==0&&f[i][j]>g)
						g=f[i][j],X=i,Y=j;
			return make_pair(X,Y);
		}
		pair<int, int> do_playChess()
		{
			int lin=0;
			for(int i=1; i<=n; i++) for(int j=1; j<=n; j++) f[i][j]=0, lin += (a[i][j] != 0);
			if(lin==0) return make_pair(n/2+1, n/2+1);
			for(int i = 1; i<=n; i++) for(int j = 1; j<=m; j++) if(a[i][j] == 0)
			{
				a[i][j] = role;
				f[i][j] = calc_value();
				a[i][j] = 0;
			}
			return get_max_pos();
		}
};

namespace Entity7
{
	Entity7_do P[3];
	void entity_startGame(chessBoard &Boa, GameType &cn, int cm)
	{
		P[cm].startGame(cn, cm, Boa);
	}
	pair<int, int> entity_playChess(chessBoard &B, GameType &G, int cm)
	{
		return P[cm].playChess();
	}
	void entity_setPos(pair<int, int> pos, int cm, int targ)
	{
		P[targ].setPos(pos, cm);
	}
	void entity_endGame(int cn, int cm)
	{
		P[cm].endGame(cn);
	}
	void entity_input(EntityControl::Player &cn)
	{
		cn.startGame = entity_startGame;
		cn.playChess = entity_playChess;
		cn.setPos = entity_setPos;
		cn.endGame = entity_endGame;
	}
}

#endif

